package com.birdboot.core;

import com.birdboot.annotations.Controller;
import com.birdboot.annotations.RequestMapping;

import java.io.File;
import java.lang.reflect.Method;
import java.net.URISyntaxException;
import java.util.HashMap;
import java.util.Map;

/*
* SpringMVC框架使用这个类来维护所有Controller
* */
public class HandlerMapping {
    private static File baseDir; //类加载路径
    /*
    * 请求与对应的处理方法的映射关系
    * key：请求路径(与对应方法上@RequestMapping注解参数一致)
    * value:处理该请求的方法
    * */
    private static Map<String, Method> mapping = new HashMap<>();
    static {
        try {
            baseDir = new File(
                    HandlerMapping.class.getClassLoader().getResource(".").toURI()
            );
            initMapping();
        } catch (URISyntaxException e) {
            e.printStackTrace();
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
    }
    /*
    * 初始化mapping
    * */
    private static void initMapping() throws ClassNotFoundException {
        File dir = new File(baseDir,"com/birdboot/controller");
        //获取该目录下的所有.class文件
        File[] subs = dir.listFiles(f->f.getName().endsWith(".class"));
        for (File sub:subs){ //遍历每一个.class文件
            String fileName = sub.getName(); //获取文件名
            String className = fileName.substring(0,sub.getName().indexOf(".")); //根据文件名获取类名
            //包名的层级分割使用"."
            Class cls = Class.forName("com.birdboot.controller."+className);
            //判断该类有没有注解Controller
            if(cls.isAnnotationPresent(Controller.class)){
                //扫描该类的所有方法
                Method[] methods = cls.getDeclaredMethods();
                //遍历每一个方法
                for (Method method:methods){
                    //判断该方法是否有注解RequestMapping
                    if(method.isAnnotationPresent(RequestMapping.class)){
                        //获取注解
                        RequestMapping rm = method.getAnnotation(RequestMapping.class);
                        //通过注解对象获取参数
                        String value = rm.value();
                        //将该方法与其处理的请求路径以key，value形式存入mapping
                        mapping.put(value,method);

                    }
                }
            }
        }
    }
    public static Method getMethod(String path){
        return  mapping.get(path);
    }

    public static void main(String[] args) {
        Method method = getMethod("/regUser");
        System.out.println(method);
    }
}
